package v1

import (
	"encoding/json"
	"github.com/gin-gonic/gin"
	"maya-service/bll"
	"maya-service/model"
	"maya-service/model/po"
	"maya-service/server/web/middleware"
	"maya-service/utils"
	"maya-service/utils/request"
)

var QuanxiRecord = &quanxiRecord{}

func init() {
	RegisterRouter(QuanxiRecord)
}

type quanxiRecord struct{}

// Init
func (a *quanxiRecord) Init(r *gin.RouterGroup) {
	g := r.Group("/quanxiRecord", middleware.Auth())
	{
		g.POST("/create", a.create)
		g.POST("/update", a.update)
		g.POST("/list", a.list)
		g.POST("/delete", a.delete)
		g.POST("/detail", a.find)
	}
}

// create
func (a *quanxiRecord) create(c *gin.Context) {
	var (
		in  = &model.QuanxiRecordCreateRequest{}
		err error
	)

	if err = c.ShouldBindJSON(in); err != nil {
		c.Error(err)
		return
	}

	// 获取用户ID
	userId, err := request.GetUserId(c.Request.Context())
	if err != nil {
		c.Error(err)
		return
	}
	in.UserId = userId

	if err = bll.QuanxiRecord.Create(c.Request.Context(), in); err != nil {
		c.Error(err)
		return
	}
	utils.ResponseOk(c, nil)
}

// update
func (a *quanxiRecord) update(c *gin.Context) {
	var (
		in  = &model.QuanxiRecordUpdateRequest{}
		err error
	)

	if err = c.ShouldBindJSON(in); err != nil {
		c.Error(err)
		return
	}

	if err = bll.QuanxiRecord.Update(c.Request.Context(), in); err != nil {
		c.Error(err)
		return
	}
	utils.ResponseOk(c, nil)
}

// list
func (a *quanxiRecord) list(c *gin.Context) {
	var (
		in  = &model.QuanxiRecordListRequest{}
		out = &model.QuanxiRecordListResponse{}
		err error
	)

	if err = c.ShouldBindJSON(in); err != nil {
		c.Error(err)
		return
	}

	// 获取用户ID
	if in.UserId == nil || *in.UserId == "" {
		userId, err := request.GetUserId(c.Request.Context())
		if err != nil {
			c.Error(err)
			return
		}
		in.UserId = &userId
	}

	// 列表数据
	if out, err = bll.QuanxiRecord.List(c.Request.Context(), in); err != nil {
		c.Error(err)
		return
	}

	var questionIds []int64
	for i := 0; i < len(out.List); i++ {
		questionIds = append(questionIds, out.List[i].QuestionId)
	}

	list, _ := bll.QuanxiQuestion.List(c.Request.Context(), &model.QuanxiQuestionListRequest{
		Ids: questionIds,
	})

	quanxiQuestionMap := make(map[int64]*po.QuanxiQuestionInfoRsp)
	if len(list.List) > 0 {
		for i := 0; i < len(list.List); i++ {
			var options []*po.QuanxiOption
			json.Unmarshal([]byte(list.List[i].Options), &options)
			quanxiQuestionMap[list.List[i].Id] = &po.QuanxiQuestionInfoRsp{
				Id:       list.List[i].Id,
				Question: list.List[i].Question,
				Options:  options,
				Type:     list.List[i].Type,
				Created:  list.List[i].CreatedAt,
				Updated:  list.List[i].UpdatedAt,
			}
		}
	}

	ret := &po.QuanxiRecordListResponse{
		Total: out.Total,
	}
	for i := 0; i < len(out.List); i++ {
		data := &po.QuanxiRecordInfo{
			QuanxiRecord:   out.List[i],
			QuanxiQuestion: nil,
		}

		if _, ok := quanxiQuestionMap[out.List[i].QuestionId]; ok {
			data.QuanxiQuestion = quanxiQuestionMap[out.List[i].QuestionId]
		}

		ret.List = append(ret.List, data)
	}

	if in.UserId != nil {
		ret.UnReadCount = bll.QuanxiRecord.Count(c.Request.Context(), *in.UserId)
	}
	utils.ResponseOk(c, ret)
}

// list
func (a *quanxiRecord) find(c *gin.Context) {
	var (
		in  = &model.QuanxiRecordInfoRequest{}
		out = &model.QuanxiRecordInfo{}
		err error
	)

	if err = c.ShouldBindJSON(in); err != nil {
		c.Error(err)
		return
	}

	if in.IsRead {
		alreadyRead := 1
		bll.QuanxiRecord.Update(c.Request.Context(), &model.QuanxiRecordUpdateRequest{
			Id:     in.Id,
			Status: &alreadyRead,
		})
	}

	if out, err = bll.QuanxiRecord.Find(c.Request.Context(), in); err != nil {
		c.Error(err)
		return
	}

	ret := &po.QuanxiRecordInfo{}
	find, _ := bll.QuanxiQuestion.Find(c.Request.Context(), &model.QuanxiQuestionInfoRequest{
		Id: out.QuestionId,
	})

	if find != nil {
		var options []*po.QuanxiOption
		json.Unmarshal([]byte(find.Options), &options)
		ret.QuanxiRecord = out
		ret.QuanxiQuestion = &po.QuanxiQuestionInfoRsp{
			Id:       find.Id,
			Question: find.Question,
			Options:  options,
			Type:     find.Type,
			Created:  find.CreatedAt,
			Updated:  find.UpdatedAt,
		}
	}
	utils.ResponseOk(c, ret)
}

// delete
func (a *quanxiRecord) delete(c *gin.Context) {
	var (
		in  = &model.QuanxiRecordDeleteRequest{}
		err error
	)

	if err = c.ShouldBindJSON(in); err != nil {
		c.Error(err)
		return
	}

	if err = bll.QuanxiRecord.Delete(c.Request.Context(), in); err != nil {
		c.Error(err)
		return
	}
	utils.ResponseOk(c, nil)
}
